package net.simflow.swf.analyzer.exec.stats.opt;

import java.util.ArrayList;
import java.util.Collection;
import java.util.HashMap;
import java.util.Map;
import java.util.TreeMap;
import java.util.Map.Entry;

import net.simflow.swf.analyzer.exec.stats.data.ServiceWaitTime;
import net.simflow.swf.analyzer.network.data.Service;

public class ServiceWaitTimeAnalyzer {

	private static ServiceWaitTimeAnalyzer instance = new ServiceWaitTimeAnalyzer();

	private ServiceWaitTimeAnalyzer() {
	}

	public static ServiceWaitTimeAnalyzer getInstance() {
		return instance;
	}

	public HashMap<Service, ServiceWaitTime> analyzeWaitTime(
			Collection<? extends Service> serviceSet) {
		HashMap<Service, ServiceWaitTime> map = new HashMap<Service, ServiceWaitTime>();

		if (serviceSet == null) {
			return map;
		}

		for (Service svc : serviceSet) {
			map.put(svc,
					new ServiceWaitTime(svc, svc.getMaxWaitTime(), svc
							.getMinWaitTime(), svc.getAvgWatiTime()));
		}

		return map;
	}

	public TreeMap<Integer, ArrayList<Service>> analyzeMaxWaitTimeDistribution(
			Map<Service, ServiceWaitTime> waiTimeMap) {
		TreeMap<Integer, ArrayList<Service>> map = new TreeMap<Integer, ArrayList<Service>>();

		if (waiTimeMap == null) {
			return map;
		}

		for (Entry<Service, ServiceWaitTime> en : waiTimeMap.entrySet()) {
			Service svc = en.getKey();
			int time = en.getValue().getMaxTime();
			ArrayList<Service> a = map.get(time);
			if (a == null) {
				a = new ArrayList<Service>();
				map.put(time, a);
			}
			a.add(svc);
		}
		map.comparator();

		return map;
	}

	public TreeMap<Integer, ArrayList<Service>> analyzeMinWaitTimeDistribution(
			Map<Service, ServiceWaitTime> waiTimeMap) {
		TreeMap<Integer, ArrayList<Service>> map = new TreeMap<Integer, ArrayList<Service>>();

		if (waiTimeMap == null) {
			return map;
		}

		for (Entry<Service, ServiceWaitTime> en : waiTimeMap.entrySet()) {
			Service svc = en.getKey();
			int time = en.getValue().getMinTime();
			ArrayList<Service> a = map.get(time);
			if (a == null) {
				a = new ArrayList<Service>();
				map.put(time, a);
			}
			a.add(svc);
		}
		map.comparator();

		return map;
	}

	public TreeMap<Double, ArrayList<Service>> analyzeAvgWaitTimeDistribution(
			Map<Service, ServiceWaitTime> waiTimeMap) {
		TreeMap<Double, ArrayList<Service>> map = new TreeMap<Double, ArrayList<Service>>();

		if (waiTimeMap == null) {
			return map;
		}

		for (Entry<Service, ServiceWaitTime> en : waiTimeMap.entrySet()) {
			Service svc = en.getKey();
			double time = en.getValue().getAvgTime();
			ArrayList<Service> a = map.get(time);
			if (a == null) {
				a = new ArrayList<Service>();
				map.put(time, a);
			}
			a.add(svc);
		}
		map.comparator();

		return map;
	}
}
